home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Shareware Overload Trio 2
/
Shareware Overload Trio Volume 2 (Chestnut CD-ROM).ISO
/
dir24
/
psi110g.zip
/
MAILCLI.C
< prev
next >
Wrap
C/C++ Source or Header
|
1994-08-26
|
10KB
|
407 lines
/* Mail Command Line Interface -- Clients
* Copyright 1992 William Allen Simpson
* partly based on a MAIL client design by Anders Klemets, SM0RGV
*
* Mods by PA0GRI
* Improved param cracking
*/
#include <ctype.h>
#include <time.h>
#include "global.h"
#include "timer.h"
#include "proc.h"
#include "socket.h"
#include "domain.h"
#include "cmdparse.h"
#include "files.h"
#include "netuser.h"
#include "mailcli.h"
#include "mailutil.h"
#include "smtp.h"
/* Tracing levels:
0 - no tracing
1 - serious errors reported
2 - transient errors reported
3 - session progress reported
*/
unsigned short Mailtrace = 1;
#ifdef MAILCLIENT
int Mailquiet = FALSE;
#ifdef LZW
int poplzw = TRUE;
#endif
struct mailservers *Mailservers = NULLMAIL;
static int domsquiet __ARGS((int argc,char *argv[],void *p));
static int domstrace __ARGS((int argc,char *argv[],void *p));
static int doadds __ARGS((int argc,char *argv[],void *p));
static int dodrops __ARGS((int argc,char *argv[],void *p));
static int dokicks __ARGS((int argc,char *argv[],void *p));
static int dolists __ARGS((int argc,char *argv[],void *p));
#ifdef LZW
static int dopoplzw __ARGS((int argc,char *argv[],void *p));
#endif
static void mailtick __ARGS((void *tp));
static char mreaderr[] = "popmail: Missing";
static struct cmds Mailcmds[] = {
"addserver", doadds, 0, 2, "popmail addserver <mailserver>"
" [<seconds>] [hh:mm-hh:mm] "
#ifdef POP2CLIENT
"pop2"
#endif
#ifdef POP3CLIENT
#ifdef POP2CLIENT
"|"
#endif
"pop3"
#endif
" <mailbox> <username> <password>",
"dropserver", dodrops, 0, 2, "popmail dropserver <mailserver>",
"kick", dokicks, 0, 2, "popmail kick <mailserver>",
"list", dolists, 0, 0, NULLCHAR,
#ifdef LZW
"lzw", dopoplzw, 0, 0, NULLCHAR,
#endif
"quiet", domsquiet, 0, 0, NULLCHAR,
"trace", domstrace, 0, 0, NULLCHAR,
NULLCHAR,
};
#ifdef LZW
static
int dopoplzw(argc,argv,p)
int argc;
char *argv[];
void *p;
{
return setbool(&poplzw,"pop lzw",argc,argv);
}
#endif
int
domsread(argc,argv,p)
int argc;
char *argv[];
void *p;
{
return subcmd(Mailcmds,argc,argv,p);
}
static int
domsquiet(argc,argv,p)
int argc;
char *argv[];
void *p;
{
return setbool(&Mailquiet,"mail quiet",argc,argv);
}
#endif
static int
domstrace(argc, argv, p)
int argc;
char *argv[];
void *p;
{
return setshort(&Mailtrace,"mail tracing",argc,argv);
}
#ifdef MAILCLIENT
static int
doadds(argc,argv,p)
int argc;
char *argv[];
void *p;
{
struct mailservers *np;
char *fullname;
int i;
int32 addr;
fullname = domainsuffix(argv[1]);
if((addr = resolve(fullname)) == 0L){
tprintf("Unknown host %s\n",fullname);
/* domainsuffix() ALLOCATED memory !, so free it - WG7J */
free(fullname);
return 1;
}
i = 2;
np = (struct mailservers *) callocw(1,sizeof(struct mailservers));
np->hostname = fullname;
np->next = Mailservers;
Mailservers = np;
np->lowtime = np->hightime = -1;
np->timer.func = mailtick; /* what to call on timeout */
np->timer.arg = (void *)np;
if( argc > i && isdigit(*argv[i])){
if(strchr(argv[i],'-') == NULLCHAR )
/* set timer duration */
set_timer(&np->timer,atol(argv[i++])*1000L);
}
if( argc > i && isdigit(*argv[i])){
int lh, ll, hh, hl;
sscanf(argv[i++], "%d:%d-%d:%d", &lh, &ll, &hh, &hl);
np->lowtime = lh * 100 + ll;
np->hightime = hh * 100 + hl;
}
if ( argc > i ) {
struct daemon *dp = Mailreaders;
for ( ; dp->name != NULLCHAR ; dp++ ) {
if ( stricmp(dp->name, argv[i]) == 0 ) {
np->reader = dp;
break;
}
}
if ( np->reader == NULLDAEMON ) {
tprintf("unrecognized protocol '%s'\n", argv[i] );
goto quit;
}
i++;
} else {
tprintf("%s protocol\n",mreaderr);
goto quit;
}
if ( argc > i ) {
np->mailbox = strdup(argv[i++]);
} else {
tprintf("%s mailbox\n",mreaderr);
goto quit;
}
if ( argc > i ) {
np->username = strdup(argv[i++]);
} else {
tprintf("%s username\n",mreaderr);
goto quit;
}
if ( argc > i ) {
np->password = strdup(argv[i++]);
} else {
char poppass[20];
tputs("Enter POP password: ");
usflush(Curproc->output);
if(recvline(Curproc->input, poppass, sizeof(poppass)) == -1)
goto quit;
rip(poppass);
np->password = strdup(poppass);
}
start_timer(&np->timer); /* and fire it up */
return 0;
quit:
Mailservers = np->next;
free(np->hostname);
free(np->username);
free(np->password);
free(np->mailbox);
free((char *)np);
return -1;
}
static int
dodrops(argc,argv,p)
int argc;
char *argv[];
void *p;
{
struct mailservers *np, *npprev = NULLMAIL;
char *fullname;
fullname = domainsuffix(argv[1]);
for (np = Mailservers; np != NULLMAIL; npprev = np, np = np->next) {
if(strnicmp(np->hostname,fullname,strlen(fullname)) == 0) {
stop_timer(&np->timer);
free(np->hostname);
free(np->username);
free(np->password);
free(np->mailbox);
if(npprev != NULLMAIL)
npprev->next = np->next;
else
Mailservers = np->next;
free((char *)np);
return 0;
}
}
tputs("No such server enabled.\n");
return -1;
}
static int
dolists(argc,argv,p)
int argc;
char *argv[];
void *p;
{
struct mailservers *np;
for (np = Mailservers; np != NULLMAIL; np = np->next) {
char tbuf[80];
if (np->lowtime != -1 && np->hightime != -1)
sprintf(tbuf, " %02d:%02d-%02d:%02d",
np->lowtime/100,
np->lowtime%100,
np->hightime/100,
np->hightime%100);
else
tbuf[0] = '\0';
tprintf("%-32s (%lu/%lu%s) %s %s\n",
np->hostname,
read_timer(&np->timer) /1000L,
dur_timer(&np->timer) /1000L,
tbuf,
np->reader->name,
np->username );
}
return 0;
}
static int
dokicks(argc,argv,p)
int argc;
char *argv[];
void *p;
{
struct mailservers *np;
char *fullname;
fullname = domainsuffix(argv[1]);
for (np = Mailservers; np != NULLMAIL; np = np->next) {
if(strnicmp(np->hostname,fullname,strlen(fullname)) == 0) {
if(availmem() - np->reader->stksize < Memthresh){
tputs("insufficient memory\n");
return 1;
}
/* If the timer is not running, the timeout function
* has already been called, and we don't want to call
* it again.
*/
if ( np->timer.duration == 0
|| run_timer(&np->timer) ) {
stop_timer(&np->timer);
newproc( np->reader->name,
np->reader->stksize,
np->reader->fp,
0, np, NULL,0);
}
return 0;
}
}
tputs("No such server enabled.\n");
return -1;
}
static void
mailtick(tp)
void *tp;
{
struct mailservers *np = tp;
struct tm *ltm;
time_t t;
int now;
if(availmem() - np->reader->stksize < Memthresh){
/* Memory is tight, don't do anything */
if (Mailtrace >= 2)
log(-1,"%s tick exit -- low memory",
np->reader->name);
start_timer(&np->timer);
return;
}
time(&t);
ltm = localtime(&t);
now = ltm->tm_hour * 100 + ltm->tm_min;
if (np->lowtime < np->hightime) { /* doesn't cross midnight */
if (now < np->lowtime || now >= np->hightime) {
if (Mailtrace >= 2)
log(-1,"%s window to '%s' not open",
np->reader->name,
np->hostname);
start_timer(&np->timer);
return;
}
} else {
if (now < np->lowtime && now >= np->hightime) {
if (Mailtrace >= 2)
log(-1,"%s window to '%s' not open",
np->reader->name,
np->hostname);
start_timer(&np->timer);
return;
}
}
newproc( np->reader->name, np->reader->stksize, np->reader->fp,
0, tp, NULL,0);
}
int
mailresponse(s,buf,comment)
int s; /* Socket index */
char *buf; /* User buffer */
char *comment; /* comment for error message */
{
if (recvline(s,buf,RLINELEN) != -1) {
if ( Mailtrace >= 3 ) {
rip(buf);
log(s,"%s <== %s", comment, buf);
}
return 0;
}
if ( Mailtrace >= 2 )
log(s,"receive error for %s response", comment);
return -1;
}
/* Check to see if mailbox is already busy (or perpetually locked) */
int
mailbusy( np )
struct mailservers *np;
{
int countdown = 10;
while ( mlock( Mailspool, np->mailbox ) ) {
if ( --countdown > 0 ) {
pause( 60000L ); /* 60 seconds */
} else {
start_timer(&np->timer);
return TRUE;
}
}
/* release while processing */
rmlock( Mailspool, np->mailbox );
return FALSE;
}
#endif